import os
import logging
import wsgiref.handlers
import hashlib
import re
import random
#import modapplyaccount #werkt niet om de 1 of andere reden
from google.appengine.api import mail
from google.appengine.ext import webapp
from google.appengine.ext.webapp import template
from util.sessions import Session
from appengine_utilities import sessions
from google.appengine.ext import db



# zie http://www.daniweb.com/tutorials/tutorial238544.html en http://code.activestate.com/recipes/65215-e-mail-address-validation/


# A Model for a User
class User(db.Model):
  account = db.StringProperty()
  password = db.StringProperty()
  emailaddress = db.StringProperty()
  name = db.StringProperty()
  timestamp = db.DateTimeProperty(auto_now_add=True)
  activated = db.BooleanProperty()
  activationhash = db.StringProperty()



# A Model for a ChatMessage
class ChatMessage(db.Model):
  user = db.ReferenceProperty()
  text = db.StringProperty()
  created = db.DateTimeProperty(auto_now=True)

# A helper for sending mail...

def doSendMail(tostr="wj.vandenbrink@gmail.com", subjectstr="bericht", bodystr="goed zo"):
  mail.send_mail(sender="wj.vandenbrink@gmail.com", 
    to=tostr, 
    subject=subjectstr, 
    body=bodystr)

	
# A helper to do the rendering and to add the necessary
# variables for the _base.htm template


def doRender(handler, tname = 'index.htm', values = { }):
  temp = os.path.join(
      os.path.dirname(__file__),
      'templates/' + tname)
  if not os.path.isfile(temp):
    return False

  # Make a copy of the dictionary and add the path and session
  newval = dict(values)
  newval['path'] = handler.request.path
  handler.session = Session()
  if 'username' in handler.session:
     newval['username'] = handler.session['username']

  outstr = template.render(temp, newval)
  handler.response.out.write(outstr)
  return True

class LoginHandler(webapp.RequestHandler):

  def get(self):
    doRender(self, 'loginscreen.htm')

  def post(self):
    self.session = Session()
    acct = self.request.get('account')
    pw = self.request.get('password')
    logging.info('Checking account='+acct+' pw='+pw)

    self.session.delete_item('username')
    self.session.delete_item('userkey')

    if pw == '' or acct == '':
      doRender(
          self,
          'loginscreen.htm',
          {'error' : 'Please specify Account and Password'} )
      return

    que = db.Query(User)
    que = que.filter('account =',acct)
    que = que.filter('password = ',pw)

    results = que.fetch(limit=1)

    if len(results) > 0 :
      user = results[0]
      self.session['userkey'] = user.key()
      self.session['username'] = acct
      doRender(self,'index.htm',{ } )
    else:
      doRender(
          self,
          'loginscreen.htm',
          {'error' : 'Incorrect password'} )

class ApplyHandler(webapp.RequestHandler):

  def get(self):
    doRender(self, 'applyscreen.htm')

  def post(self):
    self.session = Session()
    
    name = self.request.get('name')
    acct = self.request.get('account')
    pw = self.request.get('password')
    email = self.request.get('emailaddress')
    logging.info('Adding account='+acct)
    pattern = r"^[_.0-9a-z-]+@([0-9a-z][0-9a-z-]+.)+[a-z]{2,4}$"
    mail = 'l'
    rexp = re.compile(pattern)
    if pw == '' or acct == '' or name == '' or email == '':
      doRender(
          self,
          'applyscreen.htm',
          {'name' : name, 'account' : acct, 'password' : pw,'emailaddress' : email, 'error' : 'Please fill in all fields'} )
      return

	# Check emailaddress
    if  not rexp.match(email):
    #if re.match("^.+\\@(\\[?)[a-zA-Z0-9\\-\\.]+\\.([a-zA-Z]{2,3}|[0-9]{1,3})(\\]?)$", email) != None:

      doRender(
          self,
          'applyscreen.htm',
          {'name' : name, 'account' : acct, 'password' : pw,'emailaddress' : email, 'error' : 'verkeerd'} )
      return

		
	

    # Check if the user already exists
    que = db.Query(User).filter('account =',acct)
    results = que.fetch(limit=1)

    if len(results) > 0 :
      doRender(
          self,
          'applyscreen.htm',
          {'name' : name, 'account' : acct, 'password' : pw,'emailaddress' : email, 'error' : 'Account already exists!'} )
      return

    # Create the User object and log the user in
    # First, make activationhash to email to the emailaddress voor account activation
    extraseed = random.sample(['a', 'b', 'c', 'd', 'e', 'f'], 5)
    seed = ''.join(extraseed)
    activationcode = hashlib.sha1(seed + email).hexdigest()
    activationurl = "http://localhost:8080/activateacct/" + acct + ".htm" + "?acct=" + acct + "&activateacct=" + activationcode
    # Now send activationcode to emailaddress
    
    doSendMail("wj.vandenbrink@gmail.com","activation account", activationurl)
    newuser = User(name=name, account=acct, password=pw, emailaddress=email, activated=False, activationhash=activationcode);
    pkey = newuser.put();

    self.session['username'] = acct
    self.session['userkey'] = pkey
    doRender(self,'index.htm',{ })

class ActivateacctHandler(webapp.RequestHandler):
  def get(self):
    activateacct = self.request.get('activateacct')
    #plopppp = str(activateacctr)
    #activateacctp = plopppp.replace('<', '')
    #activateacct = activateacctp.replace('>', '')
    actacct = self.request.get('acct')
    quer = User.gql("WHERE account = :1", actacct)
    querdus = quer.get()
    if querdus.account == actacct and querdus.activationhash==activateacct and querdus.activated==False:
       querdus.activated = True
       querdus.put()
       plop = 'and your account is now activated!'
    elif querdus.account == actacct and querdus.activationhash==activateacct and querdus.activated==True:
       #querdus.activated = True
       #querdus.put()
       plop = 'but this account has been activated before already!'
    elif querdus.account != actacct or querdus.activationhash!=activateacct:
       #querdus.activated = True
       #querdus.put()
       plop = 'but authorisation failed:something is wrong your activation link,no activation possible!'
    #plop = querdus.timestamp
    #activationstatus = querdus.activated
    #querdus.activated =  not activationstatus
    #querdus.put()
    doRender(self, 'stophoestActivationStatus.html', {'error' : 'account ' + actacct + ' : ' + str(plop)} )


class MembersHandler(webapp.RequestHandler):

  def get(self):
    que = db.Query(User)
    user_list = que.fetch(limit=100)
    doRender(
        self,
        'memberscreen.htm', 
        {'user_list': user_list})

class ChatHandler(webapp.RequestHandler):

  def get(self):
    doRender(self,'chatscreen.htm')

  def post(self):
    self.session = Session()
    if not 'userkey' in self.session:
      doRender(
          self,
          'chatscreen.htm',
          {'error' : 'Must be logged in'} )
      return

    msg = self.request.get('message')
    if msg == '':
      doRender(
          self,
          'chat.htm',
          {'error' : 'Blank message ignored'} )
      return

    newchat = ChatMessage(user = self.session['userkey'], text=msg)
    newchat.put();
    doRender(self,'chatscreen.htm')

class MessagesHandler(webapp.RequestHandler):

  def get(self):
    que = db.Query(ChatMessage).order('-created');
    chat_list = que.fetch(limit=100)
    doRender(self, 'messagelist.htm', {'chat_list': chat_list})

class LogoutHandler(webapp.RequestHandler):

  def get(self):
    self.session = Session()
    self.session.delete_item('username')
    self.session.delete_item('userkey')
    doRender(self, 'index.htm')

class StoppedsmokingHandler(webapp.RequestHandler):

  def get(self):
    
    doRender(self, 'stoppedsmoking.html')

class ApplyAccountHandler(webapp.RequestHandler):

  def get(self):
    
    doRender(self, 'stophoestApplyAccount.html')
  
  def post(self):
    self.session = Session()
    
    name = self.request.get('name')
    acct = self.request.get('account')
    pw = self.request.get('password')
    email = self.request.get('emailaddress')
    logging.info('Adding account='+acct)
    patternemail = r"^[_.0-9a-z-]+@([0-9a-z][0-9a-z-]+.)+[a-z]{2,4}$"
    patternname = r"[\'a-zA-Z .\-]"
    patternacct = r"[\'a-zA-Z0-9.\-]"
    patterpw = r"[a-zA-Z0-9_]"
    mail = 'l'
    rexpmail = re.compile(patternemail)
    rexpname = re.compile(patternname)
    rexpacct = re.compile(patternacct)
    rexppw = re.compile(patterpw)
    if pw == '' or acct == '' or name == '' or email == '':
      doRender(
          self,
          'stophoestApplyAccount.html',
          {'name' : name, 'account' : acct, 'password' : pw,'emailaddress' : email, 'error' : 'Please fill in all fields'} )
      return


    if  not rexpname.match(name):

      doRender(
          self,
          'stophoestApplyAccount.html',
          {'name' : name, 'account' : acct, 'password' : pw,'emailaddress' : email, 'error' : 'faulty name'} )
      return
    if  not rexpacct.match(acct):

      doRender(
          self,
          'stophoestApplyAccount.html',
          {'name' : name, 'account' : acct, 'password' : pw,'emailaddress' : email, 'error' : 'faulty nickname'} )
      return

	# Check emailaddress
    if  not rexpmail.match(email):
    #if re.match("^.+\\@(\\[?)[a-zA-Z0-9\\-\\.]+\\.([a-zA-Z]{2,3}|[0-9]{1,3})(\\]?)$", email) != None:

      doRender(
          self,
          'stophoestApplyAccount.html',
          {'name' : name, 'account' : acct, 'password' : pw,'emailaddress' : email, 'error' : 'faulty emailaddress'} )
      return
    if  not rexppw.match(pw):

      doRender(
          self,
          'stophoestApplyAccount.html',
          {'name' : name, 'account' : acct, 'password' : pw,'emailaddress' : email, 'error' : 'faulty password'} )
      return


		
	

    # Check if the user already exists
    que = db.Query(User).filter('account =',acct)
    results = que.fetch(limit=1)

    if len(results) > 0 :
      doRender(
          self,
          'stophoestApplyAccount.html',
          {'name' : name, 'account' : acct, 'password' : pw,'emailaddress' : email, 'error' : 'Account already exists!'} )
      return

    # Create the User object and log the user in
    # First, make activationhash to email to the emailaddress voor account activation
    extraseed = random.sample(['a', 'b', 'c', 'd', 'e', 'f'], 5)
    seed = ''.join(extraseed)
    activationcode = hashlib.sha1(seed + email).hexdigest()
    #activationurl = "http://localhost:8080/activateacct/" + acct + ".htm" + "?acct=" + acct + "&activateacct=" + activationcode
    #activationurl = "http://worldworldorg.appspot.com/activateacct/" + acct + ".htm" + "?acct=" + acct + "&activateacct=" + activationcode
    # Now send activationcode to emailaddress
    
    doSendMail(email, "activation account", activationurl)
    newuser = User(name=name, account=acct, password=pw, emailaddress=email, activated=False, activationhash=activationcode);
    pkey = newuser.put();

    self.session['username'] = acct
    self.session['userkey'] = pkey
    doRender(self,'stophoestThanks.html',{ })



class MailHandler(webapp.RequestHandler):

  def get(self):
    hashcode = hashlib.sha1("Nobody inspects the spammish repetition").hexdigest()
    
    mail.send_mail(sender="wouterhier@localhost", 
      	to="wj.vandenbrink@gmail.com>", 
      	subject="graompaart", 
      	body="http://localhost:8080/?activate=" + hashcode)
    self.response.out.write(hashlib.sha1("Nobody inspects the spammish repetition").hexdigest())

#class TestHandler(webapp.RequestHandler):
  #def get(self):
    # print wsgiref.util.request_uri(self)???
    # print  os.environ['SERVER_NAME']  + os.environ['SERVER_PORT'] + os.environ['QUERY_STRING'] 
    # helaas werken er veel van de invironvariabelen niet hier: moet url hard-coden helaas
class MainHandler(webapp.RequestHandler):

  def get(self):
    if doRender(self,self.request.path) :
      return
    doRender(self,'index2.html')

def main():
  application = webapp.WSGIApplication([
     #('/login', LoginHandler),
     #('/apply', ApplyHandler),
     ('/applyaccount', ApplyAccountHandler),
     ('/activateacct/.*', ActivateacctHandler),
     #('/members', MembersHandler),
     #('/chat', ChatHandler),
     #('/messages', MessagesHandler),
     #('/logout', LogoutHandler),
     #('/stoppedsmoking', StoppedsmokingHandler),
     ('/mail', MailHandler),
     #('/test.htm', TestHandler),
     ('/.*', MainHandler)],
     debug=True)
  wsgiref.handlers.CGIHandler().run(application)

if __name__ == '__main__':
  main()
